/*
 * The MIT License
 *
 * Copyright 2014 Venkat Ram Akkineni.
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */
package org.netbeans.modules.tfsnb.tfvc.workingfolder.treeview;

import com.microsoft.tfs.core.TFSTeamProjectCollection;
import com.microsoft.tfs.core.clients.versioncontrol.VersionControlClient;
import com.microsoft.tfs.core.clients.versioncontrol.soapextensions.ItemSet;
import com.microsoft.tfs.core.clients.versioncontrol.soapextensions.RecursionType;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.tree.TreeSelectionModel;
import org.netbeans.modules.tfsnb.tfvc.workingfolder.treeview.nodes.ItemWrapper;
import org.openide.explorer.ExplorerManager;
import org.openide.explorer.ExplorerUtils;
import org.openide.explorer.view.BeanTreeView;
import org.openide.util.Lookup;
import org.netbeans.modules.tfsnb.tfvc.workingfolder.treeview.ServerItemTreeBuilder.*;
import org.openide.nodes.AbstractNode;
import org.openide.nodes.Children;
import org.openide.util.RequestProcessor;
import org.openide.util.Task;
import org.openide.util.TaskListener;

/**
 *
 * @author Venkat Ram Akkineni
 */
public final class WorkingFolderServerItemTreeViewPanel extends javax.swing.JPanel implements ExplorerManager.Provider, Lookup.Provider {
    
    /**
     * Creates new form WorkingFolderServerItemTreeView
     */
    public WorkingFolderServerItemTreeViewPanel(final VersionControlClient vcc, final TFSTeamProjectCollection teamProjectCollection) {
        this.versionControlClient = vcc;
        this.teamProjectCollection = teamProjectCollection;
        initComponents();
        
        /**
         * Add actions here. 
         * Example: http://bits.netbeans.org/dev/javadoc/org-openide-explorer/org/openide/explorer/ExplorerUtils.html
         */
        lookup = ExplorerUtils.createLookup(getExplorerManager(), getActionMap());
    }

    /**
     * This method is called from within the constructor to initialize the form. WARNING: Do NOT modify this code. The
     * content of this method is always regenerated by the Form Editor.
     */
    @SuppressWarnings("unchecked")
    // <editor-fold defaultstate="collapsed" desc="Generated Code">//GEN-BEGIN:initComponents
    private void initComponents() {

        workingFolderServerItemTreeViewPanelScrollPane = new BeanTreeView();
        ((BeanTreeView)workingFolderServerItemTreeViewPanelScrollPane).setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);

        setLayout(new java.awt.BorderLayout());

        workingFolderServerItemTreeViewPanelScrollPane.setBorder(javax.swing.BorderFactory.createEtchedBorder());
        add(workingFolderServerItemTreeViewPanelScrollPane, java.awt.BorderLayout.CENTER);
    }// </editor-fold>//GEN-END:initComponents

    @Override
    public void updateUI() {
        super.updateUI();
    }
    
    public void buildServerFolderExplorerManager() {
        final RequestProcessor rp = new RequestProcessor(WorkingFolderServerItemTreeViewPanel.class);
        final Map<String, ItemWrapper> itemTree;
        
        final RetrieveServerItemsThread retrieveServerItemsThread = new RetrieveServerItemsThread(){
            
            private Map<String, ItemWrapper> itemTree;
            
            @Override
            public void run() {
                showProgressBar = true;
                ItemSet itemSet = versionControlClient.getItems("$/", RecursionType.FULL);
                try {
                    itemTree = getServerItemTreeBuilder().constructTFVCItemTree(itemSet);
                } catch (UnknownFileTypeException | IncompleteItemTreeException ex) {
                    LOG.log(Level.INFO, ex.getMessage());
                }
            }

            @Override
            public Map<String, ItemWrapper> getItemTree() {
                return itemTree;
            }
        };
        
        final RequestProcessor.Task task = rp.create(retrieveServerItemsThread);
        
        task.addTaskListener(new TaskListener() {
            @Override
            public void taskFinished(Task task) {
                final Map<String, ItemWrapper> itemTree = retrieveServerItemsThread.getItemTree();
                getExplorerManager().setRootContext(new TeamProjectCollectionNode(itemTree.get("$"), teamProjectCollection.getName()));
                showProgressBar = false;
            }
        });
        
        setLoadingMessage();
        task.schedule(0);
    }

    @Override
    public ExplorerManager getExplorerManager() {
        if(explorerManager == null ) {
            explorerManager = new ExplorerManager();
        }
        return explorerManager;
    }

    @Override
    public Lookup getLookup() {
        return lookup;
    }
    
    public ServerItemTreeBuilder getServerItemTreeBuilder() {
        if(itemTreeBuilder == null) {
            itemTreeBuilder = new ServerItemTreeBuilder(versionControlClient);
        }
        return itemTreeBuilder;
    }
    
    public void setVersionControlClient(final VersionControlClient vcc) {
        this.versionControlClient = vcc;
    }
    
    public boolean showProgressBar = false;
    private final TFSTeamProjectCollection teamProjectCollection;
    private static final Logger LOG = Logger.getLogger(WorkingFolderServerItemTreeViewPanel.class.getName());
    public static final String PROGRESS_TEXT = "Retrieving source control items from server..."; 
    private VersionControlClient versionControlClient;
    private ExplorerManager explorerManager;
    private final Lookup lookup;
    private ServerItemTreeBuilder itemTreeBuilder;
    // Variables declaration - do not modify//GEN-BEGIN:variables
    private javax.swing.JScrollPane workingFolderServerItemTreeViewPanelScrollPane;
    // End of variables declaration//GEN-END:variables

    private void setLoadingMessage() {
        getExplorerManager().setRootContext(new AbstractNode(Children.LEAF){
            
            @Override
            public String getDisplayName() {
                return PROGRESS_TEXT;
            }

            @Override
            public String getName() {
                return PROGRESS_TEXT;
            }
            
        });
    }

    private interface RetrieveServerItemsThread extends Runnable {
        Map<String, ItemWrapper> getItemTree();
    }

}
